<?php
namespace QuestionPlus\QuestionPlusBundle\Controller;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;

use Topxia\WebBundle\Controller\BaseController;

use Topxia\Common\ArrayToolkit;

class QuestionPlumberController extends BaseController
{
    public function indexAction (Request $request, $courseId, $type)
    {
        $course = $this->getCourseService()->tryManageCourse($courseId);

        $questionPlusSetting = $this->getSettingService()->get('question_plus', array());

        if($request->getMethod() == 'POST'){
            $file = $request->files->get('importFile');
            $fields = $request->request->all();

            if (!$this->isTargetAollow($course, $fields['target'])) {
                throw new \RuntimeException('导入范围不存在');
            }
            $fields['type'] = 'mix';

            $path = $this->getQuestionPlumberService()->getQuestionFilePath($file, $course);

            try {
                $questions = $this->getQuestionPlumberService()->questionImport($fields['target'], $fields['type'], $path);
                
            } catch (\Exception $e) {
                    return $this->render('QuestionPlusBundle:QuestionPlumber:import-error.html.twig', array(
                    'message' => $e->getMessage()
                ));
            }

            $this->getQuestionPlumberService()->cleanQuestionFile($path);

            $questions = empty($questions) ? null : $questions;

            return $this->render('QuestionPlusBundle:Question:question-list.html.twig', array(
                'course' => $course,
                'type' => $type,
                'questions' => $questions,
                'questionsCount' => count($questions), // @todo 搞mao?
            ));
        }

        $targetsChoices = $this->getQuestionTargetChoices($course);

        $examples['mix'] = "{$this->container->getParameter('topxia.upload.public_url_path')}/plugins/question-plumber/mix.txt";
        $examples['block'] = "{$this->container->getParameter('topxia.upload.public_url_path')}/plugins/question-plumber/block.txt";

        return $this->render('QuestionPlusBundle:QuestionPlumber:' . $type . '-content.html.twig', array(
            'course' => $course,
            'type' => $type,
            'targetsChoices' => $targetsChoices,
            'examples' => $examples,
            'questionPlusSetting' => $questionPlusSetting
        ));
    }

    public function importQuestionAction (Request $request, $courseId)
    {
        $course = $this->getCourseService()->tryManageCourse($courseId);

        $questionPlusSetting = $this->getSettingService()->get('question_plus', array());

        if (!$questionPlusSetting['enabled']) {
            throw new \RuntimeException('导入功能已关闭');
        }

        //安全问题
        $questions = $request->request->get('questions');
        $questions = json_decode($questions);

        $questions = array_map(function($typeQuestions){
            return array_map(function($question){
                $question = (array)$question;
                if ($question['type'] == 'material') {
                    $question['questions'] = array_map(function($subQuestion){
                        return (array)$subQuestion;
                    }, $question['questions']);
                }

                return $question;
            }, $typeQuestions);
        }, (array)$questions);

        try {
            $count = $this->getQuestionPlumberService()->createQuestions($questions);
            return $this->createJsonResponse($count);
        } catch (\Exception $e) {
            return $this->createJsonResponse(false);
        }
    }

    public function exportQuestionAction (Request $request, $courseId)
    {
        $course = $this->getCourseService()->tryManageCourse($courseId);
        $fields = $request->request->all();

        $questionPlusSetting = $this->getSettingService()->get('question_plus', array());

        if (!$questionPlusSetting['enabled']) {
            throw new \RuntimeException('导入功能已关闭');
        }

        $conditions = ArrayToolkit::parts($fields, array('target', 'type'));

        if ($conditions['target'] == "course-{$course['id']}") {
            $conditions['targetPrefix'] = "course-{$course['id']}";
        }

        $questionCount = $this->getQuestionService()->searchQuestionsCount($conditions);

        $questions = $this->getQuestionService()->searchQuestions(
            $conditions,
            array('createdTime' ,'DESC'),
            0,
            $questionCount
        );

        if ($conditions['type'] == 'material') {
            $subQuestions = $this->getQuestionService()->findQuestionsByParentIds(ArrayToolkit::column($questions, 'id'));

            $questions = array_merge($questions, $subQuestions);
        }

        $questions = $this->filterQuestion($conditions['type'], $questions);

        list($questions, $lessonIds) = $this->targetFilter($questions);

        $lessons = $this->getCourseService()->findLessonsByIds($lessonIds);

        $questionCategories = $this->getQuestionService()->findCategoriesByIds(ArrayToolkit::column($questions, 'categoryId'));

        $response =  $this->render('QuestionPlusBundle:Question:question-export.html.twig', array(
            'questions' => $questions,
            'exportDate' => time(),
            'course' => $course,
            'lessons' => $lessons,
            'questionCategories' => $questionCategories
        ));

        $html = $response->getContent();

        if (strlen($html) < 300) {
            $difference = 300 - strlen($html);
            for ($i=0; $i < $difference; $i++) { 
                $html .= "&nbsp;";
            }
        }

        $word = $this->getQuestionPlumberService()->htmlToWord($html);

        $word = chr(239) . chr(187) . chr(191) . $word;

        $filename = '题目批量导出结果.doc';
        $filename = urlencode($filename);
        $response = new Response();
        $response->headers->set('Content-type', 'application/doc');
        $response->headers->set('Content-Disposition', 'attachment; filename="'.$filename.'"');
        $response->headers->set('Content-length', strlen($word));
        $response->setContent($word);

        return $response;
    }

    private function filterQuestion($type, $questions)
    {
        $questions = ArrayToolkit::index($questions, 'id');

        foreach ($questions as $id => $question) {
            if ($question['parentId'] == 0) {
                continue;
            }

            if (empty($type) or $type == 'material') {
                if (!array_key_exists('questions', $questions[$question['parentId']])) {
                    $questions[$question['parentId']]['questions'] = array();
                }
                $questions[$question['parentId']]['questions'][$id] = $question;
            }

            unset($questions[$id]);
        }

        return $questions;
    }

    private function targetFilter($questions)
    {
        $ids = array();
        foreach ($questions as $key => $question) {
            $target = explode('/', $question['target']);

            if (count($target) > 1) {
                list($type, $id) = explode('-', $target[1]);
                $questions[$key]['lesson'] = $id;
                $ids[] = $id;
            } else {
                $questions[$key]['lesson'] = null;
            }
        }

        return array($questions, $ids);
    }

    private function getQuestionTargetChoices($course)
    {
        $lessons = $this->getCourseService()->getCourseLessons($course['id']);
        $choices = array();
        $choices["course-{$course['id']}"] = '本课程';
        foreach ($lessons as $lesson) {
            if ($lesson['type'] == 'testpaper') {
                continue;
            }
            $choices["course-{$course['id']}/lesson-{$lesson['id']}"] = "课时{$lesson['number']}：{$lesson['title']}";
        }

        return $choices;
    }

    private function isTargetAollow($course, $target)
    {
        $choices = $this->getQuestionTargetChoices($course);

        return in_array($target, array_keys($choices));
    }

    protected function getQuestionPlumberService()
    {
        return $this->getServiceKernel()->createService('QuestionPlus:QuestionPlus.QuestionPlumberService');
    }

    private function getCourseService()
    {
        return $this->getServiceKernel()->createService('Course.CourseService');
    }

    private function getQuestionService()
    {
        return $this->getServiceKernel()->createService('Question.QuestionService');
    }

    protected function getSettingService()
    {
        return $this->getServiceKernel()->createService('System.SettingService');
    }
}